// promise
// 1. 用法 2. 周边方法 3.原理
// 解决的方法：1. 解决异步并发问题（Promise.all）2. 解决回调地狱问题（上一个输出是下一个的输入）3.错误处理比较方便
// 缺陷：依旧是基于回调函数，无法中断
/*
  用法要点：
    1. Promise是个构造函数，需要new来调用，传入一个函数 executor，这个函数会立即执行
    2. executor接收两个两个参数resolve, reject
    3. 默认创建一个promise，状态就是pending，fulfilled，rejected，
      默认是 pending （等待状态）
      成功的时候调用resolve()，传递一个成功的原因，状态就会变成 fulfilled
      失败的时候调用reject()，传递一个失败的原因，状态就会变成 rejected
      状态一旦改变（变成成功态或失败态），是不可逆
    4. 每个promise实例都有一个then，接收两个参数（onfulfilled, onrejected），成功的回调和失败的回调
    5. 如果发生异常，也会走 reject
    6. 同一个promise实例可以then多个（发布订阅模式）
    7. then可以链式调用，每次返回的新的返回promise（状态不可逆，因为要保证状态能修改，所以每次要返回一个新的promise）
      1). 如果then方法中（成功或失败）返回的不是一个promise，会将这个值传递到外层下一次的then的成功结果
      2). 如果then方法抛异常，就走到下一个then的失败回调里面
      3). 如果then方法返回的是一个promise，则这个promise的返回结果就决定下一个then的成功或失败
      只有两种情况会走下一个then失败的回调：1.出错了，异常；2. 返回的promise出错了
      其他情况都会走下一个then的成功回调
*/

const Promise = require('./promise.js');

let p1 = new Promise(function (resolve, reject) {
  // resolve(1);
  reject(2);
  // throw new Error('报错了');
});

/* p1.then(
  (res) => {
    console.log(res, 'success');
    // throw new Error('错误了');
    return new Promise(function (resolve, reject) {
      resolve(
        new Promise(function (resolve, reject) {
          resolve(
            new Promise(function (resolve, reject) {
              setTimeout(function () {
                resolve(400);
              }, 1000);
            })
          );
        })
      );
    });
  },
  (err) => {
    console.log(err, 'error');
    return 200;
  }
).then(
  (res) => {
    console.log(res, 'then2 success');
  },
  (err) => {
    console.log(err, 'then2 error');
  }
); */

p1.then()
  .then()
  .then(
    (res) => {
      console.log(res, '最后一个');
    },
    (err) => {
      console.log(err, '最后一个err');
    }
  );
